#pragma once

#include <functional>
#include <memory>
#include <netinet/in.h>
#include <string>
#include "Buffer.hpp"

class EventLoop;
class Channel;

class TcpConnection : public std::enable_shared_from_this<TcpConnection> {
public:
    using TcpConnectionPtr = std::shared_ptr<TcpConnection>;
    using ConnectionCallback = std::function<void(const TcpConnectionPtr&)>;
    using MessageCallback = std::function<void(const TcpConnectionPtr&, std::string&)>;
    using CloseCallback = std::function<void(const TcpConnectionPtr&)>;

    TcpConnection(EventLoop* loop, int sockfd, const sockaddr_in& peerAddr);
    ~TcpConnection();

    void setConnectionCallback(const ConnectionCallback& cb) { connectionCallback_ = cb; }
    void setMessageCallback(const MessageCallback& cb)       { messageCallback_ = cb; }
    void setCloseCallback(const CloseCallback& cb) { closeCallback_ = cb; }

    void connectEstablished(); // 连接建立后调用（注册读事件等）
    void handleRead();         // 可读事件回调
    void handleClose();        // 对端关闭
    void handleError();        // 错误事件

    void send(const std::string& msg);  // 主动发送数据
    void handleMsg(const std::string& msg);
    void shutdown();                    // 关闭连接

    int fd() const;
private:
    void handleWrite();  // 可写事件回调
private:
    EventLoop* loop_;
    int sockfd_;
    sockaddr_in peerAddr_;
    std::unique_ptr<Channel> channel_;

    Buffer inputBuffer_;
    Buffer outputBuffer_;
    bool connected_;

    ConnectionCallback connectionCallback_;
    MessageCallback messageCallback_;
    CloseCallback closeCallback_;
};
